/*
 * hash2text.cpp
 *
 *  Created on: Oct 29, 2012
 *      Author: m
 */

#include <iostream>
#include <string>
#include <sstream>
#include <fstream>
#include <cstring>
#include <exception>
#include "HashFile.h"

#define _TD_PARAM 5
#define _ATTR_DELIM ';'

void invalid_args()
{
    std::cerr << "Argumentos inválidos. " << std::endl
            << "Uso: hash2text hashfile outFile"
            << std::endl;
    exit( 1 );
}

typedef struct
{
    size_t id;
    std::string phrase;
    std::string surname;
    std::string name;

    bool parseData( std::string &line )
    {
        std::stringstream ss( line );

        char c;
        if ( !( ss >> id && ss >> c && c == _ATTR_DELIM ) )
            return false;

        if ( !getline( ss, phrase, _ATTR_DELIM ) )
            return false;

        if ( !getline( ss, surname, _ATTR_DELIM ) )
            return false;

        if ( !getline( ss, name, _ATTR_DELIM ) )
            name.clear();

        return true;
    }

} HashRegisterBuffer_t;

typedef struct
{
    size_t id;
    size_t td;

    bool parseID( std::string &line )
    {
        std::stringstream ss;
        std::string StringBuffer;

        if ( line.empty() )
            return false;

        ss.str( line );

        if ( !( ss >> StringBuffer && StringBuffer.compare( "bucket" ) == 0 && ss >> id && id > 0 ) )
            return false;

        return true;
    }

    bool parseTD( std::string &line )
    {
        std::stringstream ss;
        std::string StringBuffer;

        if ( line.empty() )
            return false;

        ss.str( line );

        if ( !( ss >> StringBuffer && StringBuffer.compare( "td" ) == 0 && ss >> td ) )
            return false;

        return true;
    }

} HashBucketBuffer_t;

int main( int argc, char* argv[] )
{
    std::unique_ptr<HashFile> hf;
    bucket_ptr bucket;
    std::string hashFileName;
    int bucketCounter = 1;
    bool continueReadingBuckets = true;

    if ( argc != 3 )
        invalid_args();

    hashFileName = argv[1];
    std::string textFileName = argv[2];

    hf.reset( new HashFile( hashFileName ) );
    std::ofstream textFile( textFileName.c_str(), std::ios_base::trunc );

    while( continueReadingBuckets )
    {
        try
        {
            bucket = hf->getBucket( bucketCounter );
            bucketCounter++;
        }
        catch( std::exception &e )
        {
            continueReadingBuckets = false;
            continue;
        }

        // Imprimo información de control del bucket
        textFile << "bucket " << bucket->getBucketNr() << std::endl;
        textFile << "td " << bucket->getTd() << std::endl;

        // Imprimo los registros contenidos en el bucket

        HashBucket::HR_LIST::iterator it;
        HashBucket::HR_LIST content = bucket->getContent();

        for ( it = content.begin(); it != content.end(); it++  )
        {
            textFile << (*it)->getId()    << _ATTR_DELIM
                     << (*it)->getFrase() << _ATTR_DELIM
                     << (*it)->getAutorApellido();

            if ( !( (*it)->getAutorNombre().empty() ) )
                textFile << _ATTR_DELIM << (*it)->getAutorNombre();

            textFile << std::endl;
        }

    }

    textFile.close();

    return 0;
}



